/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package Interfaz;

import CellWorld.Cell;
import CellWorld.CellWorld;
import CellWorld.CellWorldPosition;
import MDP.MDP;
import MDP.MDPRewardFunction;
import MDP.MDPTransition;
import MDP.MDPTransitionModel;
import MDP.MDPUtilityFunction;
import clases.Acciones;
import clases.State;
import java.awt.Image;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.ArrayList;
import java.util.List;
import javax.swing.Icon;
import javax.swing.ImageIcon;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import utiles.datastructure.Pair;

/**
 *
 * @author eduardo      
 */
public class ConstructorPrincipal {

    private UIPrincipal pp;
    private int filas = 6;
    private int columnas = 8;
    private double recompensa = 0;
    private CellWorld celda1;
    private CellWorld celda2;
    private CellWorld tablero1;
    float tiempoInvertidoSegs = 0.0f;
    //private Cell celda;
    private MDPRewardFunction valorRecompensa;
    private MDPTransition transicion;
    private MDPTransitionModel modelotransision;
    private Acciones accion;
    private State estado1;
    private MDP mdp;
    private Object jj;
    private MDP tablero;
    private List<JLabel> estados = new ArrayList<JLabel>();
    private List<CellWorldPosition> estadoFinal;
    private MDPUtilityFunction utilidadDeLosEstados;
    private Double utilidadEstadoinicial;
    private CellWorldPosition celdaInicial;
    List<Cell> blockedCells;
    public static final String LEFT = "left";
    public static final String RIGHT = "right";
    public static final String UP = "up";
    public static final String DOWN = "down";
    public static final String NO_OP = "no_op";
    private CellWorldPosition celdaSalida;
    private CellWorldPosition estadoAEnviar;
    private List<CellWorldPosition> estadosConUtilidad;
    private List<CellWorldPosition> estadosConUtilidad22;
    private List<CellWorldPosition> estadosSinUtilidad;
    private List<CellWorldPosition> todosLosEstados;
    private CellWorldPosition celdaTerminacion;
    public double utilidadUP, utilidadDOWN, utilidadRIGHT, utilidadLEFT;
    long tiempo;
    private int movrestantes = 12;
    private int puntos = 0;

    public ConstructorPrincipal() throws InterruptedException {

        pp = new UIPrincipal();
        pp.setTitle("Sistema de Inteligencia Artificial");
        pp.getCasilla1().setLocation(1, 1);
        pp.getCasilla2().setLocation(2, 1);
        pp.getCasilla3().setLocation(3, 1);
        pp.getCasilla4().setLocation(4, 1);
        pp.getCasilla5().setLocation(5, 1);
        pp.getCasilla6().setLocation(6, 1);
        pp.getCasilla7().setLocation(7, 1);
        pp.getCasilla8().setLocation(8, 1);
        pp.getCasilla9().setLocation(1, 2);
        pp.getCasilla10().setLocation(2, 2);
        pp.getCasilla11().setLocation(3, 2);
        pp.getCasilla12().setLocation(4, 2);
        pp.getCasilla13().setLocation(5, 2);
        pp.getCasilla14().setLocation(6, 2);
        pp.getCasilla15().setLocation(7, 2);
        pp.getCasilla16().setLocation(8, 2);
        pp.getCasilla17().setLocation(1, 3);
        pp.getCasilla18().setLocation(2, 3);
        pp.getCasilla19().setLocation(3, 3);
        pp.getCasilla20().setLocation(4, 3);
        pp.getCasilla21().setLocation(5, 3);
        pp.getCasilla22().setLocation(6, 3);
        pp.getCasilla23().setLocation(7, 3);
        pp.getCasilla24().setLocation(8, 3);
        pp.getCasilla25().setLocation(1, 4);
        pp.getCasilla26().setLocation(2, 4);
        pp.getCasilla27().setLocation(3, 4);
        pp.getCasilla28().setLocation(4, 4);
        pp.getCasilla29().setLocation(5, 4);
        pp.getCasilla30().setLocation(6, 4);
        pp.getCasilla31().setLocation(7, 4);
        pp.getCasilla32().setLocation(8, 4);
        pp.getCasilla33().setLocation(1, 5);
        pp.getCasilla34().setLocation(2, 5);
        pp.getCasilla35().setLocation(3, 5);
        pp.getCasilla36().setLocation(4, 5);
        pp.getCasilla37().setLocation(5, 5);
        pp.getCasilla38().setLocation(6, 5);
        pp.getCasilla39().setLocation(7, 5);
        pp.getCasilla40().setLocation(8, 5);
        pp.getCasilla41().setLocation(1, 6);
        pp.getCasilla42().setLocation(2, 6);
        pp.getCasilla43().setLocation(3, 6);
        pp.getCasilla44().setLocation(4, 6);
        pp.getCasilla45().setLocation(5, 6);
        pp.getCasilla46().setLocation(6, 6);
        pp.getCasilla47().setLocation(7, 6);
        pp.getCasilla48().setLocation(8, 6);
        estado1 = new State(1, 1);

        estados.add(pp.getCasilla1());
        estados.add(pp.getCasilla2());
        estados.add(pp.getCasilla3());
        estados.add(pp.getCasilla4());
        estados.add(pp.getCasilla5());
        estados.add(pp.getCasilla6());
        estados.add(pp.getCasilla7());
        estados.add(pp.getCasilla8());
        estados.add(pp.getCasilla9());
        estados.add(pp.getCasilla10());
        estados.add(pp.getCasilla11());
        estados.add(pp.getCasilla12());
        estados.add(pp.getCasilla13());
        estados.add(pp.getCasilla14());
        estados.add(pp.getCasilla15());
        estados.add(pp.getCasilla16());
        estados.add(pp.getCasilla17());
        estados.add(pp.getCasilla18());
        estados.add(pp.getCasilla19());
        estados.add(pp.getCasilla20());
        estados.add(pp.getCasilla21());
        estados.add(pp.getCasilla22());
        estados.add(pp.getCasilla23());
        estados.add(pp.getCasilla24());
        estados.add(pp.getCasilla25());
        estados.add(pp.getCasilla26());
        estados.add(pp.getCasilla27());
        estados.add(pp.getCasilla28());
        estados.add(pp.getCasilla29());
        estados.add(pp.getCasilla30());
        estados.add(pp.getCasilla31());
        estados.add(pp.getCasilla32());
        estados.add(pp.getCasilla33());
        estados.add(pp.getCasilla34());
        estados.add(pp.getCasilla35());
        estados.add(pp.getCasilla36());
        estados.add(pp.getCasilla37());
        estados.add(pp.getCasilla38());
        estados.add(pp.getCasilla39());
        estados.add(pp.getCasilla40());
        estados.add(pp.getCasilla41());
        estados.add(pp.getCasilla42());
        estados.add(pp.getCasilla43());
        estados.add(pp.getCasilla44());
        estados.add(pp.getCasilla45());
        estados.add(pp.getCasilla46());
        estados.add(pp.getCasilla47());
        estados.add(pp.getCasilla48());



        crearTablero();

        pp.getBotonAvanzar().addActionListener(new ActionListener() {

            @Override
            public void actionPerformed(ActionEvent ae) {
                avanzar();
            }
        });

        pp.getBotonPorbabilidad().addActionListener(new ActionListener() {

            @Override
            public void actionPerformed(ActionEvent ae) {
                generarProbabilidad();
            }
        });

    }

    public void crearTablero() {

        tablero1 = new CellWorld(filas, columnas, recompensa);
        CellWorldPosition estadoInicial = tablero1.getInitialState();
        System.out.println("El estado inicial es:" + estadoInicial);
        estadoFinal = tablero1.getFinalStates();

        tablero1.markBlocked(estadoFinal.get(0).getY(), estadoFinal.get(0).getX()); //le digo cual es la celda del estado final




        todosLosEstados = tablero1.getNonFinalStates();
        estadoAEnviar = estadoFinal.get(0);
        tablero1.getCelda(estadoAEnviar.getY(), estadoAEnviar.getX()).setReward(1000.0);

        estadosConUtilidad = new ArrayList<CellWorldPosition>();
        estadosConUtilidad22 = new ArrayList<CellWorldPosition>();
        estadosSinUtilidad = tablero1.getNonFinalStates();
        List<Pair<CellWorldPosition, Double>> casillasLimitrofes = setearUtilidadInicialALasCasillas(estadoAEnviar, 1000.0);

        for (Pair<CellWorldPosition, Double> pair : casillasLimitrofes) {
            estadosConUtilidad.add(pair.getFirst());
        }

        do {
            for (CellWorldPosition estadosRRecorridos : estadosConUtilidad) {

                List<Pair<CellWorldPosition, Double>> casillasCercanas = setearUtilidadInicialALasCasillas(estadosRRecorridos, tablero1.getCelda(estadosRRecorridos.getY(), estadosRRecorridos.getX()).getReward());

                for (Pair<CellWorldPosition, Double> pai : casillasCercanas) {
                    estadosConUtilidad22.add(pai.getFirst());
                }
            }
            estadosConUtilidad.clear();
            for (CellWorldPosition estadosRecorridos : estadosConUtilidad22) {

                List<Pair<CellWorldPosition, Double>> casillasMedias = setearUtilidadInicialALasCasillas(estadosRecorridos, tablero1.getCelda(estadosRecorridos.getY(), estadosRecorridos.getX()).getReward());

                for (Pair<CellWorldPosition, Double> pa : casillasMedias) {
                    estadosConUtilidad.add(pa.getFirst());
                }
            }

            estadosConUtilidad22.clear();
        } while (!todosLosEstados.isEmpty());



        tablero = new MDP(tablero1);
        utilidadDeLosEstados = tablero.valueIterationForFixedIterations(10, 0.3);



        for (Object object : estadoFinal) {
            jj = object;

            System.out.println("ESTADO FINAL :" + jj);
        }


        ////////////////////////////////////////////////////////////////////////////////////////////////
//           tablero.policyIteration(0.8);
//           tiempo = System.currentTimeMillis();
        //         System.out.println("Iteracion de politicas");

///////////////////////////////////////////////////////////////////////////////////////////////////////d

        tablero.valueIteration(0.8, 0.3, 0.0);//gamma, error, delta
        tiempo = System.currentTimeMillis();
        System.out.println("Iteracion de valores");


        pp.getCasilla1().setText("agente");
        System.out.println("El estado inicial es:" + pp.getCasilla1().getText());
        pp.getCasilla1().setOpaque(false);

//recorrer los jlabel hasta encontrar aquel que tenga la misma posicion que el estado final
        for (JLabel estado : estados) {
            if ((int) estado.getLocation().getY() == estadoFinal.get(0).getY()) {
                if ((int) estado.getLocation().getX() == estadoFinal.get(0).getX()) {
                    System.out.println("El estado final corresponde a la casilla: " + estado.getText());
                    estado.setOpaque(false);
                }
            }
        }



        for (filas = 1; filas < 7; filas++) {
            for (columnas = 1; columnas < 9; columnas++) {
                utilidadEstadoinicial = utilidadDeLosEstados.getUtility(tablero1.getCelda(filas, columnas).position());
                System.out.println("Utilidad casilla: " + tablero1.getCelda(filas, columnas).position() + " es: " + utilidadEstadoinicial);



            }
        }



        for (filas = 1; filas < 7; filas++) {
            for (columnas = 1; columnas < 9; columnas++) {
                System.out.println("Posición de la celda creada:" + tablero1.getCelda(filas, columnas).position());
                System.out.println("Recompensa :" + tablero1.getCelda(filas, columnas).getReward());
            }
        }


        celdaSalida = tablero1.getCelda(1, 1).position(); //busco la celda en la que se encuentra el agente
        pp.getCampoMovRest().setText(String.valueOf(movrestantes));
        pp.getCampoPuntos().setText(String.valueOf(0));



        
        
    }

    public void generarProbabilidad() {

        // genero un valor aleatorio entre 0.0 y 1.0
        double valorAleatorio = Math.random() * (1 - 0) + 0;

        pp.getCampoProb().setText(String.valueOf(valorAleatorio));
        pp.getBotonAvanzar().setEnabled(true);
        pp.getBotonPorbabilidad().setEnabled(false);



    }

    public void avanzar() {
        ///* 
        pp.getCasilla1().setLocation(1, 1);
        pp.getCasilla2().setLocation(2, 1);
        pp.getCasilla3().setLocation(3, 1);
        pp.getCasilla4().setLocation(4, 1);
        pp.getCasilla5().setLocation(5, 1);
        pp.getCasilla6().setLocation(6, 1);
        pp.getCasilla7().setLocation(7, 1);
        pp.getCasilla8().setLocation(8, 1);
        pp.getCasilla9().setLocation(1, 2);
        pp.getCasilla10().setLocation(2, 2);
        pp.getCasilla11().setLocation(3, 2);
        pp.getCasilla12().setLocation(4, 2);
        pp.getCasilla13().setLocation(5, 2);
        pp.getCasilla14().setLocation(6, 2);
        pp.getCasilla15().setLocation(7, 2);
        pp.getCasilla16().setLocation(8, 2);
        pp.getCasilla17().setLocation(1, 3);
        pp.getCasilla18().setLocation(2, 3);
        pp.getCasilla19().setLocation(3, 3);
        pp.getCasilla20().setLocation(4, 3);
        pp.getCasilla21().setLocation(5, 3);
        pp.getCasilla22().setLocation(6, 3);
        pp.getCasilla23().setLocation(7, 3);
        pp.getCasilla24().setLocation(8, 3);
        pp.getCasilla25().setLocation(1, 4);
        pp.getCasilla26().setLocation(2, 4);
        pp.getCasilla27().setLocation(3, 4);
        pp.getCasilla28().setLocation(4, 4);
        pp.getCasilla29().setLocation(5, 4);
        pp.getCasilla30().setLocation(6, 4);
        pp.getCasilla31().setLocation(7, 4);
        pp.getCasilla32().setLocation(8, 4);
        pp.getCasilla33().setLocation(1, 5);
        pp.getCasilla34().setLocation(2, 5);
        pp.getCasilla35().setLocation(3, 5);
        pp.getCasilla36().setLocation(4, 5);
        pp.getCasilla37().setLocation(5, 5);
        pp.getCasilla38().setLocation(6, 5);
        pp.getCasilla39().setLocation(7, 5);
        pp.getCasilla40().setLocation(8, 5);
        pp.getCasilla41().setLocation(1, 6);
        pp.getCasilla42().setLocation(2, 6);
        pp.getCasilla43().setLocation(3, 6);
        pp.getCasilla44().setLocation(4, 6);
        pp.getCasilla45().setLocation(5, 6);
        pp.getCasilla46().setLocation(6, 6);
        pp.getCasilla47().setLocation(7, 6);
        pp.getCasilla48().setLocation(8, 6);//*/

        if (celdaSalida != estadoFinal) {

            Pair<CellWorldPosition, String> movimiento = recorroCasillas(celdaSalida);

            CellWorldPosition celdaLlegada = movimiento.getFirst();

            String accion = movimiento.getSecond();


            transicion = new MDPTransition(celdaSalida, accion, celdaLlegada);


            tablero1.getTransitionProbability(celdaSalida, accion, celdaLlegada);

            System.out.println("Transición:" + transicion.toString());
            System.out.println("estado inicial:" + celdaSalida);
            System.out.println("accion:" + transicion.getAction());

            System.out.println("estado final:" + transicion.getDestinationState().toString());

            transicion.toString();
            //veo cual es la probabilidad de transicion de cada estado
            System.out.println("probabilidad de transicion:" + tablero.getTransitionProbability(transicion));

            ////////////////////////tengo que generar la probabilidad para despues compararla en el if de abajo y poder saber que direccio tomar

            if (tablero1.getTransitionProbability(celdaSalida, accion, celdaLlegada) >= Double.parseDouble(pp.getCampoProb().getText())) {


                for (JLabel estadoSalida : estados) {
                    if ((int) estadoSalida.getLocation().getY() == celdaSalida.getY()) {
                        if ((int) estadoSalida.getLocation().getX() == celdaSalida.getX()) {
                            System.out.println("La celda de salida es: " + celdaSalida);

                            for (JLabel estadoLlegada : estados) {
                                if ((int) estadoLlegada.getLocation().getY() == celdaLlegada.getY()) {
                                    if ((int) estadoLlegada.getLocation().getX() == celdaLlegada.getX()) {
                                        estadoLlegada.setOpaque(false);
                                        estadoLlegada.setText("agente");
                                        System.out.println("La celda de llegada es: " + celdaLlegada);

                                    }
                                }
                            }
                            estadoSalida.setOpaque(true);
                            estadoSalida.setText("");
                        }
                    }
                }
                //si la probabilidad esta entre 0.71 y 0.85 hace la primera accion perpendicular a la accion real
            } else if ((Double.parseDouble(pp.getCampoProb().getText()) > 0.70) && (Double.parseDouble(pp.getCampoProb().getText()) < 0.86)) {

                String accion1 = determineDireccionPerpendicular(accion, Double.parseDouble(pp.getCampoProb().getText()));
                celdaLlegada = moveFrom(celdaSalida, accion1);///celda de llegada de la primera accion perpendicular

                if ((celdaSalida.getX() == celdaLlegada.getX()) && (celdaSalida.getY() == celdaLlegada.getY())) {
                    System.out.println("No puede avanzar porque choca contra la pared, permanece en la misma celda");
                } else {

                    for (JLabel estadoSalida : estados) {
                        if ((int) estadoSalida.getLocation().getY() == celdaSalida.getY()) {
                            if ((int) estadoSalida.getLocation().getX() == celdaSalida.getX()) {
                                System.out.println("La celda de salida es: " + celdaSalida);

                                for (JLabel estadoLlegada : estados) {
                                    if ((int) estadoLlegada.getLocation().getY() == celdaLlegada.getY()) {
                                        if ((int) estadoLlegada.getLocation().getX() == celdaLlegada.getX()) {
                                            estadoLlegada.setOpaque(false);
                                            estadoLlegada.setText("agente");
                                            System.out.println("La celda de llegada es: " + celdaLlegada);

                                        }
                                    }
                                }
                                estadoSalida.setOpaque(true);
                                estadoSalida.setText("");
                            }
                        }
                    }
                }


            } else {//si la probabilidad esta entre 0.86 y 1 hace la segunda accion perpendicular a la accion real
                String accion2 = determineDireccionPerpendicular(accion, Double.parseDouble(pp.getCampoProb().getText()));
                celdaLlegada = moveFrom(celdaSalida, accion2);///celda de llegada de la segunda accion perpendicular
                if ((celdaSalida.getX() == celdaLlegada.getX()) && (celdaSalida.getY() == celdaLlegada.getY())) {
                    System.out.println("No puede avanzar porque choca contra la pared, permanece en la misma celda");
                } else {
                    for (JLabel estadoSalida : estados) {
                        if ((int) estadoSalida.getLocation().getY() == celdaSalida.getY()) {
                            if ((int) estadoSalida.getLocation().getX() == celdaSalida.getX()) {
                                System.out.println("La celda de salida es: " + celdaSalida);

                                for (JLabel estadoLlegada : estados) {
                                    if ((int) estadoLlegada.getLocation().getY() == celdaLlegada.getY()) {
                                        if ((int) estadoLlegada.getLocation().getX() == celdaLlegada.getX()) {
                                            estadoLlegada.setOpaque(false);
                                            estadoLlegada.setText("agente");
                                            System.out.println("La celda de llegada es: " + celdaLlegada);

                                        }
                                    }
                                }
                                estadoSalida.setOpaque(true);
                                estadoSalida.setText("");
                            }
                        }
                    }

                }
            }



            System.out.println("estado final = " + jj);


            celdaSalida = celdaLlegada;
  
            //verifico si quedan movimientos restantes, sino hay movimientos restantes y no alcance el estado final, termina el juego
            if ((movrestantes < 1) && ((celdaSalida.getX() != estadoFinal.get(0).getX()) || (celdaSalida.getY() != estadoFinal.get(0).getY()))) {


                ImageIcon icono = new ImageIcon("/home/edu/NetBeansProjects/tesoroEscondido/src/imagenes/perdiste.png");
                JOptionPane.showMessageDialog(pp, "Se terminaron los movimientos disponible, PERDISTE", "Mala Suerte", JOptionPane.INFORMATION_MESSAGE, icono);
                pp.setVisible(false);

            }


        } else {
            System.out.println("EL AGENTE ENCONTRO EL TESORO");
        }
        tiempo = System.currentTimeMillis() - tiempo;

        tiempoInvertidoSegs = tiempoInvertidoSegs + tiempo;

        System.out.println("Tiempo invertido: " + (tiempoInvertidoSegs / 1000));

        pp.getBotonAvanzar().setEnabled(false);
        pp.getBotonPorbabilidad().setEnabled(true);
        pp.getCampoProb().setText("");
        movrestantes = movrestantes - 1;
        puntos = puntos + 10;
        pp.getCampoMovRest().setText(String.valueOf(movrestantes));
        pp.getCampoPuntos().setText(String.valueOf(puntos));
        //ingreso la corona al estado final

            if (((celdaSalida.getX() == estadoFinal.get(0).getX()) && (celdaSalida.getY()== estadoFinal.get(0).getY()))) {


                ImageIcon icono = new ImageIcon("/home/edu/NetBeansProjects/tesoroEscondido/src/imagenes/corona.png");
                JOptionPane.showMessageDialog(pp, "Has encontrado la CORONA!!!, GANASTE!!", "Buena Suerte!!", JOptionPane.INFORMATION_MESSAGE, icono);
                pp.setVisible(false);

            }else if (((celdaSalida.getX() == 3) && (celdaSalida.getY()== 5))) {//ingreso la primera recompensa


                ImageIcon icono = new ImageIcon("/home/edu/NetBeansProjects/tesoroEscondido/src/imagenes/alas.png");
                JOptionPane.showMessageDialog(pp, "Has encontrado Alas, sumas 3 movimientos", "¡¡Buena Suerte!!", JOptionPane.INFORMATION_MESSAGE, icono);
                movrestantes = movrestantes + 3;
                pp.getCampoMovRest().setText(String.valueOf(movrestantes));


            }else if (((celdaSalida.getX() == 4) && (celdaSalida.getY()== 1))) {//ingreso la segunda recompensa


                ImageIcon icono = new ImageIcon("/home/edu/NetBeansProjects/tesoroEscondido/src/imagenes/auto.png");
                JOptionPane.showMessageDialog(pp, "Has encontrado un Auto, sumas 2 movimientos", "¡¡Buena Suerte!!", JOptionPane.INFORMATION_MESSAGE, icono);
                movrestantes = movrestantes + 2;
                pp.getCampoMovRest().setText(String.valueOf(movrestantes));

            }else if (((celdaSalida.getX() == 7) && (celdaSalida.getY()== 5))) {//ingreso la tercera recompensa


                ImageIcon icono = new ImageIcon("/home/eduo/NetBeansProjects/tesoroEscondido/src/imagenes/plata.png");
                JOptionPane.showMessageDialog(pp, "Has encontrado Dinero, sumas 1000 puntos", "¡¡Buena Suerte!!", JOptionPane.INFORMATION_MESSAGE, icono);
                puntos = puntos + 1000;
                pp.getCampoPuntos().setText(String.valueOf(puntos));
            }else if (((celdaSalida.getX() == 7) && (celdaSalida.getY()== 3))) {//ingreso el primer castigo


                ImageIcon icono = new ImageIcon("/home/edu/NetBeansProjects/tesoroEscondido/src/imagenes/soldado.png");
                JOptionPane.showMessageDialog(pp, "Has encontrado un Soldado, restas 2 movimientos", "Mala Suerte", JOptionPane.INFORMATION_MESSAGE, icono);
                movrestantes = movrestantes - 2;
                pp.getCampoMovRest().setText(String.valueOf(movrestantes));

            }else if (((celdaSalida.getX() == 3) && (celdaSalida.getY()== 3))) {//ingreso el segundo castigo


                ImageIcon icono = new ImageIcon("/home/edu/NetBeansProjects/tesoroEscondido/src/imagenes/terminator.png");
                JOptionPane.showMessageDialog(pp, "Has encontrado un Terminator, restas 3 movimientos", "Mala Suerte", JOptionPane.INFORMATION_MESSAGE, icono);
                movrestantes = movrestantes - 3;
                pp.getCampoMovRest().setText(String.valueOf(movrestantes));

            }else if (((celdaSalida.getX() == 5) && (celdaSalida.getY()== 4))) {//ingreso el tercer castigo


                ImageIcon icono = new ImageIcon("/home/edu/NetBeansProjects/tesoroEscondido/src/imagenes/inspector.png");
                JOptionPane.showMessageDialog(pp, "Has encontrado al Inspector, restas 500 puntos", "Mala Suerte", JOptionPane.INFORMATION_MESSAGE, icono);
                puntos = puntos - 500;
                pp.getCampoPuntos().setText(String.valueOf(puntos));
            }else if(((celdaSalida.getX() == 5) && (celdaSalida.getY()== 6))) {//ingreso el mamut que hace perder el juego


                ImageIcon icono = new ImageIcon("/home/edu/NetBeansProjects/tesoroEscondido/src/imagenes/mamut.png");
                JOptionPane.showMessageDialog(pp, "Has encontrado al Mamut, PERDISTE", "Fin del Juego", JOptionPane.INFORMATION_MESSAGE, icono);
                pp.setVisible(false);

            }
 


    }

    private String determineDireccionPerpendicular(String accioncommandedDirection, double probab) {
        if (probab <= 0.7) {
            return accioncommandedDirection;
        } else if ((probab > 0.7) && (probab < 0.85)) {
            if ((accioncommandedDirection.equals(LEFT)) || (accioncommandedDirection.equals(RIGHT))) {


                return UP;
            }
            if ((accioncommandedDirection.equals(UP)) || (accioncommandedDirection.equals(DOWN))) {
                return LEFT;
            }
        } else { // 0.9 < prob < 1.0
            if ((accioncommandedDirection.equals(LEFT)) || (accioncommandedDirection.equals(RIGHT))) {

                return DOWN;
            }
            if ((accioncommandedDirection.equals(UP)) || (accioncommandedDirection.equals(DOWN))) {

                return RIGHT;
            }
        }
        throw new RuntimeException(
                "Impsible determinar la dirección cuando el comando =  "
                + accioncommandedDirection + " y la probabilidad = " + probab);

    }

    public void iniciar() {

        pp.setVisible(true);
        pp.setLocationRelativeTo(null);

    }

    private boolean isBlocked(int i, int j) {
        if ((i < 1) || (i > 6) || (j < 1) || (j > 8)) {
            return true;
        }
        if (blockedCells != null) {
            for (Cell c : blockedCells) {
                if ((c.getY() == j) && (c.getX() == i)) {
                    return true;
                }
            }
        }
        return false;
    }

    public boolean isBlocked(Pair<Integer, Integer> p) {
        return isBlocked(p.getFirst(), p.getSecond());
    }

    private CellWorldPosition moveFrom(int i, int j, String direction) {
        if (direction.equals(LEFT)) {
            return moveLeftFrom(i, j);
        }
        if (direction.equals(RIGHT)) {
            return moveRightFrom(i, j);
        }
        if (direction.equals(UP)) {
            return moveUpFrom(i, j);
        }
        if (direction.equals(DOWN)) {
            return moveDownFrom(i, j);
        }
        throw new RuntimeException("Imposible mover hacia " + direction + " desde " + i
                + " , " + j);
    }

    private CellWorldPosition moveFrom(CellWorldPosition startingPosition,
            String direction) {
        return moveFrom(startingPosition.getX(), startingPosition.getY(),
                direction);
    }

    private CellWorldPosition moveLeftFrom(int i, int j) {
        if (isBlocked(j, i - 1)) {
            return tablero1.getCelda(j, i).position();
        }
        return tablero1.getCelda(j, i - 1).position();
    }

    private CellWorldPosition moveUpFrom(int i, int j) {
        if (isBlocked(j + 1, i)) {
            return tablero1.getCelda(j, i).position();
        }
        return tablero1.getCelda(j + 1, i).position();
    }

    private CellWorldPosition moveRightFrom(int i, int j) {
        if (isBlocked(j, i + 1)) {
            return tablero1.getCelda(j, i).position();
        }
        return tablero1.getCelda(j, i + 1).position();
    }

    private CellWorldPosition moveDownFrom(int i, int j) {
        if (isBlocked(j - 1, i)) {
            return tablero1.getCelda(j, i).position();
        }
        return tablero1.getCelda(j - 1, i).position();
    }

    public Pair<CellWorldPosition, String> recorroCasillas(CellWorldPosition casilla) {

        CellWorldPosition celdaArriba = moveFrom(casilla, "up");
        utilidadUP = utilidadDeLosEstados.getUtility(celdaArriba);





        CellWorldPosition celdaAbajo = moveFrom(casilla, "down");

        utilidadDOWN = utilidadDeLosEstados.getUtility(celdaAbajo);




        CellWorldPosition celdaDerecha = moveFrom(casilla, "right");

        utilidadRIGHT = utilidadDeLosEstados.getUtility(celdaDerecha);




        CellWorldPosition celdaIzquierda = moveFrom(casilla, "left");

        utilidadLEFT = utilidadDeLosEstados.getUtility(celdaIzquierda);



        double max = maximo(utilidadUP, utilidadDOWN, utilidadRIGHT, utilidadLEFT);

        if (max == utilidadUP) {

            return new Pair<CellWorldPosition, String>(celdaArriba, "up");
        } else if (max == utilidadDOWN) {
            return new Pair<CellWorldPosition, String>(celdaAbajo, "down");
        } else if (max == utilidadRIGHT) {
            return new Pair<CellWorldPosition, String>(celdaDerecha, "right");
        } else {
            return new Pair<CellWorldPosition, String>(celdaIzquierda, "left");
        }

    }

    public double maximo(double up, double down, double right, double left) {

        return Math.max(up, Math.max(down, Math.max(right, left)));
    }

    private void setUtilidadInicial(CellWorldPosition estARecorrer) {
        tablero.setReward(estARecorrer, 200.0);
    }

    public List<Pair<CellWorldPosition, Double>> setearUtilidadInicialALasCasillas(CellWorldPosition casillass, Double recompensa) {

        List<Pair<CellWorldPosition, Double>> casillasADevolver = new ArrayList<Pair<CellWorldPosition, Double>>();
        Pair<CellWorldPosition, Double> paresArriba;
        Pair<CellWorldPosition, Double> paresAbajo;
        Pair<CellWorldPosition, Double> paresDerecha;
        Pair<CellWorldPosition, Double> paresIzquierda;

        CellWorldPosition celdaArriba = moveFrom(casillass, "up");

        //pregunta si la casilla no tiene recompensa, si no tiene le setea una recompensa con el valor de la casilla principal - 100
        if (tablero1.getCelda(celdaArriba.getY(), celdaArriba.getX()).getReward() == 0.0) {

            tablero1.getCelda(celdaArriba.getY(), celdaArriba.getX()).setReward(recompensa - 100.0);

            paresArriba = new Pair<CellWorldPosition, Double>(celdaArriba, tablero1.getCelda(celdaArriba.getY(), celdaArriba.getX()).getReward());


            todosLosEstados.remove(celdaArriba);
            estadosSinUtilidad.remove(celdaArriba);

            casillasADevolver.add(paresArriba);



        };

        CellWorldPosition celdaAbajo = moveFrom(casillass, "down");

        if (tablero1.getCelda(celdaAbajo.getY(), celdaAbajo.getX()).getReward() == 0.0) {
            tablero1.getCelda(celdaAbajo.getY(), celdaAbajo.getX()).setReward(recompensa - 100.0);
            paresAbajo = new Pair<CellWorldPosition, Double>(celdaAbajo, tablero1.getCelda(celdaAbajo.getY(), celdaAbajo.getX()).getReward());
            todosLosEstados.remove(celdaAbajo);
            //estadosConUtilidad.add(celdaAbajo);
            estadosSinUtilidad.remove(celdaAbajo);

            casillasADevolver.add(paresAbajo);

        };

        CellWorldPosition celdaDerecha = moveFrom(casillass, "right");

        if (tablero1.getCelda(celdaDerecha.getY(), celdaDerecha.getX()).getReward() == 0.0) {
            tablero1.getCelda(celdaDerecha.getY(), celdaDerecha.getX()).setReward(recompensa - 100.0);
            paresDerecha = new Pair<CellWorldPosition, Double>(celdaDerecha, tablero1.getCelda(celdaDerecha.getY(), celdaDerecha.getX()).getReward());

            estadosSinUtilidad.remove(celdaDerecha);
            todosLosEstados.remove(celdaDerecha);
            casillasADevolver.add(paresDerecha);
        };

        CellWorldPosition celdaIzquierda = moveFrom(casillass, "left");

        if (tablero1.getCelda(celdaIzquierda.getY(), celdaIzquierda.getX()).getReward() == 0.0) {
            tablero1.getCelda(celdaIzquierda.getY(), celdaIzquierda.getX()).setReward(recompensa - 100.0);
            paresIzquierda = new Pair<CellWorldPosition, Double>(celdaIzquierda, tablero1.getCelda(celdaIzquierda.getY(), celdaIzquierda.getX()).getReward());

            estadosSinUtilidad.remove(celdaIzquierda);
            todosLosEstados.remove(celdaIzquierda);
            casillasADevolver.add(paresIzquierda);
        };

        return casillasADevolver;
    }
}
